```vue
<template>
  <div class="container dark-theme">
    <div class="header">
      <div class="back-button" @click="goBack">
        <i class="el-icon-arrow-left"></i> 返回
      </div>
      <div class="title">全部房屋</div>
      <div class="header-actions">
        <el-button type="primary" @click="showOrders">
          <i class="el-icon-tickets"></i> 我的租赁订单
        </el-button>
      </div>
    </div>

    <el-form ref="form" :model="form" label-width="80px">
      <el-form-item label="房屋名称">
        <el-input v-model="form.name"></el-input>
      </el-form-item>

      <el-form-item>
        <el-button @click="sumitSearch">搜索</el-button>
        <el-button @click="cancelSearch">取消</el-button>
      </el-form-item>
    </el-form>

    <div class="content">
      <div class="house-grid">
        <div v-for="house in houses" :key="house.id" class="house-card" @click="viewDetail(house)">
          <div class="house-image">
            <img :src="house.images || defaultImage" :alt="house.title">
            <div v-if="house.currentPrice < house.originalPrice" class="special-tag">特价</div>
            <div v-if="house.status === 2" class="sold-out-tag">已下架</div>
          </div>
          <div class="house-info">
            <div class="house-header">
              <h3>{{ house.title }}</h3>
              <div class="price">
                ¥{{ (house.currentPrice / 100).toFixed(2) }}/月
                <span v-if="house.currentPrice < house.originalPrice" class="original-price">
                  ¥{{ (house.originalPrice / 100).toFixed(2) }}/月
                </span>
              </div>
            </div>
            <div class="store-info">
              <i class="el-icon-shop"></i>
              <span>{{ house.ownerName || '未知房东' }}</span>
            </div>
            <div class="house-footer">
              <div class="tags">
                <span v-if="house.currentPrice < house.originalPrice" class="tag special">特价</span>
                <span v-if="isNewHouse(house.createTime)" class="tag new">新房源</span>
                <span v-if="house.status === 1" class="tag hot">热租</span>
              </div>
            </div>
          </div>
        </div>
      </div>
    </div>

    <!-- 分页组件 -->
    <div class="block">
      <el-pagination v-if="!isSearching" @current-change="handleCurrentChange" :current-page.sync="currentPage" :page-size="pageSize"
        layout="prev, pager, next, jumper" :total="totalHouses">
      </el-pagination>
    </div>

    <!-- 订单对话框 -->
    <el-dialog title="租赁订单详情" :visible.sync="ordersDialogVisible" width="70%" custom-class="orders-dialog">
      <el-table :data="orders" style="width: 100%" :header-cell-style="{ background: '#002d52', color: '#fff' }"
        :cell-style="{ background: '#fff', color: 'black' }" @selection-change="handleOrderSelectionChange">
        <el-table-column type="selection" width="50"></el-table-column>
        <el-table-column label="房屋图片" width="120">
          <template slot-scope="scope">
            <img :src="scope.row.houseImage || defaultImage" :alt="scope.row.houseTitle || ''" class="house-img">
          </template>
        </el-table-column>
        <el-table-column prop="order_id" label="订单ID" width="150"></el-table-column>
        <el-table-column prop="houseTitle" label="房屋名称"></el-table-column>
        <el-table-column prop="amount" label="租赁月份" width="100"></el-table-column>
        <el-table-column prop="currentPrice" label="单价" width="120">
          <template slot-scope="scope">
            ¥{{ (scope.row.currentPrice / 100).toFixed(2) }}/月
          </template>
        </el-table-column>
        <el-table-column label="总价" width="120">
          <template slot-scope="scope">
            ¥{{ (scope.row.totalPrice / 100).toFixed(2) }}
            <el-tooltip v-if="scope.row.totalPrice !== scope.row.currentPrice * scope.row.amount" content="后端总价数据异常，已校正"
              placement="top">
              <i class="el-icon-warning" style="color: #f56c6c; margin-left: 5px;"></i>
            </el-tooltip>
          </template>
        </el-table-column>
        <el-table-column prop="order_status" label="状态" width="100">
          <template slot-scope="scope">
            {{ getOrderStatusText(scope.row.order_status) }}
          </template>
        </el-table-column>
        <el-table-column prop="order_time" label="下单时间" width="180">
          <template slot-scope="scope">
            {{ formatDate(scope.row.order_time) }}
          </template>
        </el-table-column>
        <el-table-column prop="checkin_time" label="入住时间" width="180">
          <template slot-scope="scope">
            {{ formatDate(scope.row.checkin_time) }}
          </template>
        </el-table-column>
      </el-table>
      <div class="orders-footer">
        <div class="total-price">
          总计: ¥{{ ordersTotalPrice }}
        </div>
        <el-button type="danger" size="small" @click="refundOrder"
          :disabled="!selectedOrderItems.length || selectedOrderItems.every(item => item.order_status !== 1)"
          title="仅可退款状态为'已购买'或'已支付'的订单">
          批量退款
        </el-button>
      </div>
    </el-dialog>
  </div>
</template>

<script>
import axios from 'axios';

export default {
  name: 'HouseList',
  data() {
    return {
      form: {
        name: '',
      },
      isSearching: false, // 是否处于搜索状态

      currentPage: 1,    // 当前页码
      pageSize: 12,      // 每页显示条数
      totalHouses: 0,       // 总条数
      houses: [],
      orders: [],
      user: null,
      ordersDialogVisible: false,
      ordersTotalPrice: 0,
      selectedOrderItems: [],
      defaultImage: 'https://via.placeholder.com/150',
      imageBaseUrl: 'http://localhost:8089',
      isLoadingOrders: false,
      isRefunding: false,
    };
  },
  created() {
    this.fetchUser();
    this.handleCurrentChange(1);

  },
  methods: {
    sumitSearch() {
      axios.get(`/commodity/house/search/${this.form.name}`, {
        headers: { Authorization: `Bearer ${localStorage.getItem('token')}` },
      }).then((res) => {
        if (res.status == 200 && res.data.success){
          this.houses = res.data.data
          this.isSearching = true; // 搜索成功，隐藏分页
        } else {
          Message('搜索失败')
        }
      }).catch((err) => {
        Message('搜索失败')
        console.log('搜索失败', err)
      })
    },
    cancelSearch() {
      this.form.name = ''
      this.isSearching = false; // 恢复分页
      this.handleCurrentChange(1);
    },

    async fetchUser() {
      try {
        const { data: userData } = await axios.get('/users/user/basic', {
          headers: { Authorization: `Bearer ${localStorage.getItem('token')}` },
        });
        if (userData.success && userData.data) {
          this.user = userData.data;
        } else {
          this.$message.error('获取用户信息失败：无有效数据');
        }
      } catch (error) {
        this.$message.error('获取用户信息失败');
        console.error('获取用户信息失败:', error);
      }
    },

    async handleCurrentChange(page) { // 添加分页参数
      this.currentPage = page; // 更新当前页码
      try {
        const response = await axios.get('/commodity/house/list/pageHouse', {
          params: {
            page: this.currentPage,
            pageSize: this.pageSize
          },
          headers: { Authorization: `Bearer ${localStorage.getItem('token')}` },
        });

        if (response.data.success) {

          this.houses = response.data.data.houses;
          this.totalHouses = response.data.data.total;

          this.houses = await Promise.all(
            this.houses.map(async (house) => {
              let ownerName = '未知房东';
              try {
                const ownerResponse = await axios.get(`/commodity/owner/${house.ownerId}`, {
                  headers: { Authorization: `Bearer ${localStorage.getItem('token')}` },
                });
                if (ownerResponse.data.success && ownerResponse.data.data) {
                  ownerName = ownerResponse.data.data.name || `房东${house.ownerId}`;
                }
              } catch (ownerError) {
                console.error(`获取房东${house.ownerId}信息失败:`, ownerError);
              }
              return {
                ...house,
                ownerName,
              };
            })
          );

        } else {
          this.$message.error(response.data.errorMsg || '获取商品列表失败');
        }

      } catch (error) {
        this.$message.error('网络错误，请稍后重试');
        console.error('获取商品列表失败:', error);
      }
    },

    async fetchOrders() {
      if (!this.user?.id) {
        this.$message.error('请先登录');
        return;
      }
      if (this.isLoadingOrders) return;
      this.isLoadingOrders = true;
      const userId = this.user.id;
      try {
        const response = await axios.get(`/commodity/house-order/list/allOrder?userId=${userId}`, {
          headers: { Authorization: `Bearer ${localStorage.getItem('token')}` },
        });
        if (response.data.success) {
          if (!response.data.data || response.data.data.length === 0) {
            this.$message.info('暂无订单');
            this.orders = [];
            this.updateOrdersTotal();
            return;
          }
          this.orders = response.data.data.map((order) => {
            const calculatedTotal = order.currentPrice * order.amount;
            if (order.total !== calculatedTotal) {
              console.warn(`订单 ${order.id} 总价异常：后端返回 ${order.total}，应为 ${calculatedTotal}`);
            }
            return {
              order_id: order.id,
              houseTitle: order.title || '未知房屋',
              amount: order.amount || 1,
              currentPrice: order.currentPrice || 0,
              totalPrice: calculatedTotal,
              houseImage: order.images
                ? order.images.startsWith('http')
                  ? order.images
                  : `${this.imageBaseUrl}${order.images}`
                : this.defaultImage,
              order_status: order.status !== null ? order.status : -1,
              order_time: order.createTime || new Date().toISOString(),
              checkin_time: order.checkinTime || new Date().toISOString(),
            };
          });
          this.updateOrdersTotal();
        } else {
          this.$message.error(response.data.errorMsg || '获取订单列表失败');
        }
      } catch (error) {
        this.$message.error('网络错误，请稍后重试');
        console.error('获取订单失败:', error);
      } finally {
        this.isLoadingOrders = false;
      }
    },
    goBack() {
      this.$router.go(-1);
    },
    viewDetail(house) {
      this.$router.push(`/credit-business/house-detail/${house.id}`);
    },
    showOrders() {
      this.ordersDialogVisible = true;
      this.fetchOrders();
    },
    async refundOrder() {
      if (!this.selectedOrderItems.length) {
        this.$message.warning('请至少选择一个订单进行退款');
        return;
      }
      if (this.isRefunding) return;
      this.isRefunding = true;
      this.$confirm(`确定要退款选中的 ${this.selectedOrderItems.length} 个订单吗？`, '提示', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
        type: 'warning',
      })
        .then(async () => {
          try {
            const token = localStorage.getItem('token');
            for (const order of this.selectedOrderItems) {
              if (!order.order_id) {
                this.$message.error(`订单 ${order.houseTitle} 缺少有效的订单ID`);
                continue;
              }
              const response = await axios.post(
                `/commodity/house-order/refund?orderId=${order.order_id}`,
                {},
                { headers: { Authorization: `Bearer ${token}` } }
              );
              if (!response.data.success) {
                this.$message.error(`订单 ${order.order_id} 退款失败：${response.data.errorMsg || '未知错误'}`);
              } else {
                this.$message.success(`订单 ${order.order_id} 退款成功`);
              }
            }
            this.$message.success('退款申请处理完成');
            this.fetchOrders();
          } catch (error) {
            this.$message.error('退款请求失败：' + (error.response?.data?.errorMsg || error.message));
            console.error('退款失败:', error);
          } finally {
            this.isRefunding = false;
          }
        })
        .catch(() => {
          this.$message.info('已取消退款');
          this.isRefunding = false;
        });
    },
    handleOrderSelectionChange(selection) {
      this.selectedOrderItems = selection;
      this.updateOrdersTotal();
    },
    updateOrdersTotal() {
      this.ordersTotalPrice = this.selectedOrderItems
        .reduce((total, item) => total + (item.totalPrice / 100), 0)
        .toFixed(2);
    },
    isNewHouse(createTime) {
      if (!createTime) return false;
      const createDate = new Date(createTime);
      const now = new Date();
      const diffDays = (now - createDate) / (1000 * 60 * 60 * 24);
      return diffDays <= 7;
    },
    formatDate(date) {
      if (!date) return '未知';
      const d = new Date(date);
      return `${d.getFullYear()}-${String(d.getMonth() + 1).padStart(2, '0')}-${String(d.getDate()).padStart(2, '0')} ${String(d.getHours()).padStart(2, '0')}:${String(d.getMinutes()).padStart(2, '0')}`;
    },
    getOrderStatusText(status) {
      switch (status) {
        case 1: return '已购买';
        case 2: return '已退款';
        default: return '未知';
      }
    },
  },
};
</script>

<style scoped>
.container.dark-theme {
  background: radial-gradient(ellipse at center, #001e3c 0%, #000 100%);
  min-height: 100vh;
  color: #fff;
  font-family: 'Microsoft YaHei', sans-serif;
}

.header {
  display: flex;
  align-items: center;
  padding: 20px;
  background: #002d52;
}

.header-actions {
  display: flex;
  gap: 10px;
}

.back-button {
  cursor: pointer;
  color: #4fc3f7;
  font-size: 16px;
}

.back-button:hover {
  color: #999;
}

.title {
  margin-left: 20px;
  font-size: 20px;
  color: #fff;
  flex: 1;
}

.content {
  padding: 20px;
}

.house-grid {
  display: flex;
  flex-wrap: wrap;
  gap: 20px;
  justify-content: flex-start;
}

.house-card {
  background: rgba(0, 45, 82, 0.8);
  border-radius: 8px;
  overflow: hidden;
  transition: transform 0.3s;
  display: flex;
  flex-direction: column;
  cursor: pointer;
  width: 300px;
  min-height: 400px;
}

.house-card:hover {
  transform: translateY(-5px);
}

.house-image {
  position: relative;
  width: 100%;
  height: 200px;
}

.house-image img {
  width: 100%;
  height: 100%;
  object-fit: cover;
}

.special-tag,
.sold-out-tag {
  position: absolute;
  right: 10px;
  padding: 4px 8px;
  border-radius: 4px;
  font-size: 12px;
  font-weight: bold;
}

.special-tag {
  background: #f56c6c;
  color: #fff;
}

.sold-out-tag {
  background: #909399;
  color: #fff;
}

.house-info {
  padding: 15px;
  flex: 1;
  display: flex;
  flex-direction: column;
}

.house-header {
  display: flex;
  justify-content: space-between;
  align-items: flex-start;
  margin-bottom: 10px;
}

.house-header h3 {
  margin: 0;
  color: #fff;
  font-size: 18px;
  flex: 1;
}

.price {
  color: #f56c6c;
  font-size: 20px;
  font-weight: bold;
  margin-left: 10px;
}

.original-price {
  color: #b0bec5;
  font-size: 14px;
  text-decoration: line-through;
  margin-left: 5px;
}

.store-info {
  color: #b0bec5;
  font-size: 14px;
  margin-bottom: 10px;
  display: flex;
  align-items: center;
}

.store-info i {
  margin-right: 5px;
}

.house-footer {
  display: flex;
  justify-content: space-between;
  align-items: center;
  margin-top: auto;
}

.tags {
  display: flex;
  gap: 5px;
}

.tag {
  padding: 2px 8px;
  border-radius: 4px;
  font-size: 12px;
}

.tag.special {
  background: #f56c6c;
  color: #fff;
}

.tag.new {
  background: #67c23a;
  color: #fff;
}

.tag.hot {
  background: #e6a23c;
  color: #fff;
}

.el-button {
  background: #003b64;
  border: 1px solid #4fc3f7;
  color: #4fc3f7;
}

.el-button:hover:not(:disabled) {
  background: #4fc3f7;
  color: #fff;
}

.el-button:disabled {
  background: #909399;
  border-color: #909399;
  color: #fff;
  cursor: not-allowed;
}

.orders-dialog {
  background: #001e3c;
}

.orders-dialog .el-dialog__title {
  color: #fff;
}

.house-img {
  width: 80px;
  height: 80px;
  object-fit: cover;
  border-radius: 4px;
}

.orders-footer {
  display: flex;
  justify-content: flex-end;
  align-items: center;
  margin-top: 20px;
  padding: 20px;
  background: #002d52;
  border-radius: 4px;
}

.total-price {
  font-size: 20px;
  color: #4fc3f7;
  margin-right: 20px;
}
</style>
```
